#!/usr/bin/env python
# -*- coding: utf-8 -*-
"""
@desc: .

@Project ：kuberCloudTest 
@File ：physical_machine.py
@Author ：admin
@Date ：2024/3/21 11:31 
"""
from kuberCloudTest.common.basic import basicUtils
from kuberCloudTest.common.constant import OFFSET, LIMIT, AsyncType
from kuberCloudTest.common.utils import _getOperationType, _getDetail
from kuberCloudTest.urls import Urls


class physicalMachineUtils(basicUtils):

    def __init__(self, accessToken):
        super().__init__(accessToken)


def get_utils(accessToken):
    return physicalMachineUtils(accessToken=accessToken)


def getMachine(accessToken, **kwargs):
    """
    获取物理机
    :param accessToken: access token
    :param kwargs: limit:
                   offset:
                   keyword: xxx
                   searchItem: 0: 物理机名称; 1: 物理机uuid; 2: 物理机IP
                   nid: 网络Id
                   msid: 系统盘主存储UUID
                   hostnames: 排除的虚机名称
                   status: 就绪状态
                   state: 状态
                            1:启用  0:删除
    :return:
    """
    return get_utils(accessToken).cloud_http_request.get(Urls.getMachine.value,
                                                         {
                                                             'offset': kwargs.get('offset', OFFSET),
                                                             'limit': kwargs.get('limit', LIMIT),
                                                             'searchitem': kwargs.get('searchItem', 0),
                                                             'keyword': kwargs.get('keyword', ''),
                                                             'nid': kwargs.get('nid', ''),
                                                             'msid': kwargs.get('msid', ''),
                                                             'hostnames': kwargs.get('hostnames', ''),
                                                             'status': kwargs.get('status', ''),
                                                             'state': kwargs.get('state', ''),
                                                         })


def getMachineDetail(accessToken, machineId):
    """
    获取物理机详情
    :param accessToken:
    :param machineId: 物理机UUID
    :return:
    """
    content = getMachine(accessToken)
    total = content.get('total', 0)
    content = get_utils(accessToken).cloud_http_request.get(Urls.getMachine.value, {'limit': total, 'offset': OFFSET})
    return _getDetail(content, machineId, 'hostid')


def createMachine(accessToken, host, port, username, password, clusterId, cpuShared: bool = False, **kwargs):
    """
    创建物理机
    :param accessToken: access token
    :param host: 主机IP
    :param port: 端口
    :param username: 用户名
    :param password: 密码
    :param clusterId: 集群ID
    :param cpuShared: CPU共享;
                        True:创建在该物理机上的云主机可以绑定pCPU
                        False:创建在该物理机上的云主机不允许绑定pCPU
    :param kwargs:
                   ipmiIp: ipmi地址
                   ipmiPort: ipmi端口
                   ipmiUsername: ipmi用户名
                   ipmiPassword: ipmi密码
                   producer: 厂家
                   assetNumber: 资产编号
                   cabinetLocation: 机柜位置
                   computerRoom: 机房位置
                   director: 负责人
                   directorMobile: 负责人电话
                   remark: 描述
    :return:
    """
    operationType = 1701
    data = _getOperationType(operationType, AsyncType.ASYNC.value)

    data['hostip'] = host
    data['sshport'] = port
    data['loginid'] = username
    data['loginpw'] = password
    data['clusterid'] = clusterId
    data['cpushared'] = 'true' if cpuShared else 'false'

    data['ipmiip'] = kwargs.get('ipmiIp', '')
    data['ipmiport'] = kwargs.get('ipmiPort', '')
    data['ipmiusername'] = kwargs.get('ipmiUsername', '')
    data['ipmipassword'] = kwargs.get('ipmiPassword', '')
    data['producer'] = kwargs.get('producer', '')
    data['assetnumber'] = kwargs.get('assetNumber', '')
    data['cabinetlocation'] = kwargs.get('cabinetLocation', '')
    data['computerroom'] = kwargs.get('computerRoom', '')
    data['director'] = kwargs.get('director', '')
    data['directormobile'] = kwargs.get('directorMobile', '')

    data['remark'] = kwargs.get('remark', '')

    return get_utils(accessToken).cloud_http_request.post(Urls.createMachine.value, data)


def updateMachine(accessToken, machineId, port, username, password=None, **kwargs):
    """
    更新物理机
    :param accessToken: access token
    :param machineId: 物理机ID
    :param port: 物理机端口
    :param username: 物理机用户名
    :param password: 物理机密码
    :param kwargs:
                   ipmiIp: ipmi地址
                   ipmiPort: ipmi端口
                   ipmiUsername: ipmi用户名
                   ipmiPassword: ipmi密码
                   producer: 厂家
                   assetNumber: 资产编号
                   cabinetLocation: 机柜位置
                   computerRoom: 机房位置
                   director: 负责人
                   directorMobile: 负责人电话
                   remark: 描述
    :return:
    """
    operationType = 1707
    data = _getOperationType(operationType, AsyncType.ASYNC.value)

    data['hostid'] = machineId
    data['sshport'] = port
    data['loginid'] = username
    if password:
        data['loginpw'] = password

    data['ipmiport'] = kwargs.get('ipmiPort', '')
    data['ipmiip'] = kwargs.get('ipmiIp', '')
    data['ipmipassword'] = kwargs.get('ipmiPassword', '')
    data['ipmiusername'] = kwargs.get('ipmiUsername', '')
    data['producer'] = kwargs.get('producer', '')
    data['cabinetlocation'] = kwargs.get('cabinetLocation', '')
    data['assetnumber'] = kwargs.get('assetNumber', '')
    data['director'] = kwargs.get('director', '')
    data['computerroom'] = kwargs.get('computerRoom', '')
    data['directormobile'] = kwargs.get('directorMobile', '')

    data['remark'] = kwargs.get('remark', '')

    return get_utils(accessToken).cloud_http_request.post(Urls.updateMachine.value, data)


def startMachine(accessToken, machineId):
    """
    启动物理机
    :param accessToken: access token
    :param machineId: 物理机ID
    :return:
    """
    operationType = 1702
    data = _getOperationType(operationType, AsyncType.ASYNC.value)

    data['id'] = machineId

    return get_utils(accessToken).cloud_http_request.post(Urls.startMachine.value, data)


def stopMachine(accessToken, machineId):
    """
    停用物理机
    :param accessToken: access token
    :param machineId: 物理机ID
    :return:
    """
    operationType = 1703
    data = _getOperationType(operationType, AsyncType.ASYNC.value)

    data['id'] = machineId

    return get_utils(accessToken).cloud_http_request.post(Urls.stopMachine.value, data)


def removeMachine(accessToken, machineIds):
    """
    删除物理机
    :param accessToken: access token
    :param machineIds: 物理机UUID(多个使用英文逗号分割)
    :return:
    """
    operationType = 1706
    data = _getOperationType(operationType, AsyncType.ASYNC.value)

    data['ids'] = machineIds

    return get_utils(accessToken).cloud_http_request.post(Urls.removeMachine.value, data)


def reconnectMachine(accessToken, machineId):
    """
    重连物理机
    :param accessToken: access token
    :param machineId: 物理机ID
    :return:
    """
    operationType = 1704
    data = _getOperationType(operationType, AsyncType.ASYNC.value)

    data['id'] = machineId

    return get_utils(accessToken).cloud_http_request.post(Urls.reconnectMachine.value, data)


def powerOffMachine(accessToken, machineId):
    """
    物理机关机
    :param accessToken: access token
    :param machineId: 物理机ID
    :return:
    """
    operationType = 1722
    data = _getOperationType(operationType, AsyncType.ASYNC.value)

    data['id'] = machineId

    return get_utils(accessToken).cloud_http_request.post(Urls.powerOffMachine.value, data)


def powerOnMachine(accessToken, machineId):
    """
    物理机开机
    :param accessToken: access token
    :param machineId: 物理机ID
    :return:
    """
    operationType = 1723
    data = _getOperationType(operationType, AsyncType.ASYNC.value)

    data['id'] = machineId

    return get_utils(accessToken).cloud_http_request.post(Urls.powerOnMachine.value, data)


def rebootMachine(accessToken, machineId):
    """
    物理机重启
    :param accessToken: access token
    :param machineId: 物理机ID
    :return:
    """
    operationType = 1724
    data = _getOperationType(operationType, AsyncType.ASYNC.value)
    data['id'] = machineId

    return get_utils(accessToken).cloud_http_request.post(Urls.rebootMachine.value, data)


def maintainMachine(accessToken, machineId):
    """
    物理机进入维护模式
    :param accessToken: access token
    :param machineId: 物理机ID
    :return:
    """
    operationType = 1705
    data = _getOperationType(operationType, AsyncType.ASYNC.value)

    data['id'] = machineId

    return get_utils(accessToken).cloud_http_request.post(Urls.maintainMachine.value, data)


def getMachineByClusterId(accessToken, clusterId, **kwargs):
    """
    根据集群ID获取物理机
    :param accessToken: access token
    :param clusterId: 集群ID
    :param kwargs: limit:
                   offset:
                   keyword: xxx
    :return:
    """
    return get_utils(accessToken).cloud_http_request.get(Urls.getMachineByClusterId.value,
                                                         {
                                                             'offset': kwargs.get('offset', OFFSET),
                                                             'limit': kwargs.get('limit', LIMIT),
                                                             'keyword': kwargs.get('keyword', ''),
                                                             'clusterId': clusterId
                                                         })


def getMachineNicInfo(accessToken, machineId, **kwargs):
    """
    获取物理机网卡信息
    :param accessToken: access token
    :param machineId: 物理机ID
    :param kwargs: limit:
                   offset:
                   keyword: xxx
    :return:
    """
    return get_utils(accessToken).cloud_http_request.get(Urls.getMachineNicInfo.value,
                                                         {
                                                             'offset': kwargs.get('offset', OFFSET),
                                                             'limit': kwargs.get('limit', LIMIT),
                                                             'keyword': kwargs.get('keyword', ''),
                                                             'hostId': machineId
                                                         })


def cutMachineNicSRIOV(accessToken, networkCardId, vfsNum):
    """
    物理机网卡SR-IOV切割
    :param accessToken: access token
    :param networkCardId: 物理机网卡ID
    :param vfsNum: vfs数量
    :return:
    """
    operationType = 1710
    data = _getOperationType(operationType, AsyncType.ASYNC.value)
    params = {'nicid': networkCardId, 'vfsnum': vfsNum}
    return get_utils(accessToken).cloud_http_request.post(Urls.cutMachineNicSRIOV.value, params=params, data=data)


def revertMachineNicSRIOV(accessToken, networkCardId):
    """
    物理机网卡SR-IOV还原
    :param accessToken: access token
    :param networkCardId: 物理机网卡ID
    :return:
    """
    operationType = 1711
    data = _getOperationType(operationType, AsyncType.ASYNC.value)
    params = {'nicid': networkCardId}
    return get_utils(accessToken).cloud_http_request.post(Urls.revertMachineNicSRIOV.value, params=params, data=data)


def syncMachineNIC(accessToken, machineId):
    """
    物理机网卡信息同步
    :param accessToken: access token
    :param machineId: 物理机ID
    :return:
    """
    operationType = 1709
    data = _getOperationType(operationType, AsyncType.ASYNC.value)
    params = {'hostId': machineId}
    return get_utils(accessToken).cloud_http_request.post(Urls.syncMachineNIC.value, params=params, data=data)


def getMachineGPU(accessToken, machineId, **kwargs):
    """
    获取物理机GPU信息
    :param accessToken: access token
    :param machineId: 物理机ID
    :param kwargs: limit:
                   offset:
                   keyword: xxx
    :return:
    """
    return get_utils(accessToken).cloud_http_request.get(Urls.getMachineGPU.value,
                                                         {
                                                             'offset': kwargs.get('offset', OFFSET),
                                                             'limit': kwargs.get('limit', LIMIT),
                                                             'hostId': machineId
                                                         })


def getMachinePhysicalHardDrive(accessToken, machineId, **kwargs):
    """
    获取物理机物理硬盘信息
    :param accessToken: access token
    :param machineId: 物理机ID
    :param kwargs: limit:
                   offset:
                   keyword: xxx
    :return:
    """
    return get_utils(accessToken).cloud_http_request.get(Urls.getMachinePhysicalHardDrive.value,
                                                         {
                                                             'offset': kwargs.get('offset', OFFSET),
                                                             'limit': kwargs.get('limit', LIMIT),
                                                             'hostId': machineId
                                                         })


def getMachineLogicalHardDrive(accessToken, machineId, **kwargs):
    """
    获取物理机逻辑硬盘信息
    :param accessToken: access token
    :param machineId: 物理机ID
    :param kwargs: limit:
                   offset:
                   keyword: xxx
    :return:
    """
    return get_utils(accessToken).cloud_http_request.get(Urls.getMachineLogicalHardDrive.value,
                                                         {
                                                             'offset': kwargs.get('offset', OFFSET),
                                                             'limit': kwargs.get('limit', LIMIT),
                                                             'hostId': machineId
                                                         })


def syncMachineLogicalHardDrive(accessToken, machineId):
    """
    物理机逻辑硬盘信息同步
    :param accessToken: access token
    :param machineId: 物理机ID
    :return:
    """
    operationType = 1714
    data = _getOperationType(operationType, AsyncType.ASYNC.value)
    params = {'hostId': machineId}
    return get_utils(accessToken).cloud_http_request.post(Urls.syncMachineLogicalHardDrive.value,
                                                          params=params, data=data)


def getMachineLogicalHardDriveMountableVM(accessToken, machineId, **kwargs):
    """
    获取物理机逻辑硬盘可挂载的虚拟机
    :param accessToken: access token
    :param machineId: 物理机ID
    :param kwargs: limit:
                   offset:
                   keyword: xxx
    :return:
    """
    return get_utils(accessToken).cloud_http_request.get(Urls.getMachineLogicalHardDriveMountableVM.value,
                                                         {
                                                             'offset': kwargs.get('offset', OFFSET),
                                                             'limit': kwargs.get('limit', LIMIT),
                                                             'keyword': kwargs.get('keyword', ''),
                                                             'hostid': machineId
                                                         })


def loadVMByMachineLogicalHardDrive(accessToken, machineId, vmId, logicalHardDriveId):
    """
    物理机逻辑硬盘挂载虚拟机
    :param accessToken: access token
    :param machineId: 物理机ID
    :param vmId: 虚拟机ID
    :param logicalHardDriveId: 逻辑硬盘ID
    :return:
    """
    operationType = 1715
    data = _getOperationType(operationType, AsyncType.ASYNC.value)
    data['vmid'] = vmId
    data['hostid'] = machineId
    data['diskid'] = logicalHardDriveId

    return get_utils(accessToken).cloud_http_request.post(Urls.loadVMByMachineLogicalHardDrive.value, data=data)


def unloadVMByMachineLogicalHardDrive(accessToken, machineId, vmId, logicalHardDriveId):
    """
    物理机逻辑硬盘卸载虚拟机
    :param accessToken: access token
    :param machineId: 物理机ID
    :param vmId: 虚拟机ID
    :param logicalHardDriveId: 逻辑硬盘ID
    :return:
    """
    operationType = 1716
    data = _getOperationType(operationType, AsyncType.ASYNC.value)

    data['vmid'] = vmId
    data['hostid'] = machineId
    data['diskid'] = logicalHardDriveId

    return get_utils(accessToken).cloud_http_request.post(Urls.unloadVMByMachineLogicalHardDrive.value, data=data)


def configMachineCpuShare(accessToken, machineId, cpuShare: bool = False):
    """
    配置物理机CPU共享
    :param accessToken: access token
    :param machineId: 物理机ID
    :param cpuShare: CPU共享值
                        True: 共享；
                        False: 取消共享
    :return:
    """
    if cpuShare:
        operationType = 1725
        data = _getOperationType(operationType, AsyncType.ASYNC.value)
        data['cpushared'] = 'true'
    else:
        operationType = 1726
        data = _getOperationType(operationType, AsyncType.ASYNC.value)
        data['cpushare'] = 'false'
    data['hostid'] = machineId

    return get_utils(accessToken).cloud_http_request.post(Urls.configMachineCpuShare.value, data=data)


def getMachineHugePage(accessToken, machineId, **kwargs):
    """
    获取物理机内存大页规格信息
    :param accessToken: access token
    :param machineId: 物理机ID
    :param kwargs: limit:
                   offset:
                   keyword: xxx
    :return:
    """
    return get_utils(accessToken).cloud_http_request.get(Urls.getMachineHugePage.value,
                                                         {
                                                             'offset': kwargs.get('offset', OFFSET),
                                                             'limit': kwargs.get('limit', LIMIT),
                                                             'hostId': machineId
                                                         })


def createMachineHugePage(accessToken, machineId, hugePageSize: int, hugePageUnit: int):
    """
    创建物理机内存大页
    :param accessToken: access token
    :param machineId: 物理机ID
    :param hugePageSize: 大页大小
    :param hugePageUnit: 页大小单位
                            1: GB
                            2: MB
    :return:
    """
    operationType = 1727
    data = _getOperationType(operationType, AsyncType.ASYNC.value)
    data['hostId'] = machineId
    data['pageSize'] = hugePageSize
    data['pageSizeUnit'] = hugePageUnit
    return get_utils(accessToken).cloud_http_request.post(Urls.createMachineHugePage.value, data=data)


def deleteMachineHugePage(accessToken, hugePageIds):
    """
    删除物理机内存大页
    :param accessToken: access token
    :param hugePageIds: 大页ID(多个使用英文逗号分割)
    :return:
    """
    operationType = 1728
    data = _getOperationType(operationType, AsyncType.ASYNC.value)
    data['ids'] = hugePageIds
    return get_utils(accessToken).cloud_http_request.post(Urls.deleteMachineHugePage.value, data=data)
